#include <PinDebouncer.h>
#include <PushButton.h>

int globalPushButtonPin = 8;

PushButton
  globalPB(globalPushButtonPin);

unsigned long globalMinimumTimeBetweenDebounceSamplesUs = 20;
const unsigned int globalDebounceFilterBufferArraySize = 8;
unsigned char globalDebounceFilterBufferArray[globalDebounceFilterBufferArraySize];

PinDebouncer
  globalPD(
    globalPushButtonPin,
    globalMinimumTimeBetweenDebounceSamplesUs,
    globalDebounceFilterBufferArray,
    globalDebounceFilterBufferArraySize);

int globalLEDPin = 13;

unsigned char OnDigitalRead(unsigned int pinNumber, void* object)
{
  if (object)
  {
    return (static_cast<PinDebouncer*>(object))->GetPinState();
  }
  else
  {
    return digitalRead(pinNumber);
  }
}

void setup()
{
  pinMode(globalLEDPin, OUTPUT);
  
  digitalWrite(globalLEDPin, HIGH);
  delay(250);
  digitalWrite(globalLEDPin, LOW);
  delay(250);
  digitalWrite(globalLEDPin, HIGH);
  delay(250);
  digitalWrite(globalLEDPin, LOW);
  
  globalPB.OnDigitalRead(OnDigitalRead, &globalPD);
}

void loop()
{
    globalPD.Service();

    switch(globalPB.Service())
    {
      case PushButton::SINGLE_PUSH:
        {
          digitalWrite(globalLEDPin, digitalRead(globalLEDPin) == HIGH ? LOW : HIGH);
          delay(200);
          digitalWrite(globalLEDPin, digitalRead(globalLEDPin) == HIGH ? LOW : HIGH);
        }
        break;
      case PushButton::DOUBLE_PUSH:
        {
          digitalWrite(globalLEDPin, digitalRead(globalLEDPin) == HIGH ? LOW : HIGH);
        }
        break;
      case PushButton::CONSTANT_PUSH:
        {
            Blink(1000);
        }
        break;
      case PushButton::CONSTANT_PUSH2:
        {
            Blink(250);
        }
        break;
      default:
        {
          // digitalWrite(globalLEDPin, LOW);
        }
        break;
    }
}

int globalDelayCounterMs = 0;

void Blink(int intervalMs)
{
  // if (globalBlinkEnabled)
  {
    int _currentCounterMs = millis();
    
    if ((_currentCounterMs - globalDelayCounterMs) > intervalMs)
    {
      digitalWrite(globalLEDPin, digitalRead(globalLEDPin) == HIGH ? LOW : HIGH);
      globalDelayCounterMs = _currentCounterMs;
    }
  }
}

